package com.ykan.ykds.ctrl.driver.fsk;

import java.io.IOException;
import java.nio.IntBuffer;

import android.media.AudioFormat;
import android.media.AudioManager;
import android.media.AudioTrack;
import android.util.Log;

import com.ykan.ykds.ctrl.driver.fsk.FSKEncoder.FSKEncoderCallback;


public class FSKPlayer {

	protected FSKConfig mConfig;
	protected FSKEncoder mEncoder;
	protected AudioTrack mAudioTrack;
	private String TAG = FSKPlayer.class.getSimpleName();
    public int pwMinBufferSize = 0;
	
	public FSKPlayer(){
		try {
			pwMinBufferSize = AudioTrack.getMinBufferSize(FSKConfig.SAMPLE_RATE_44100,  AudioFormat.CHANNEL_OUT_STEREO,   AudioFormat.ENCODING_PCM_8BIT);
			mConfig = new FSKConfig(FSKConfig.SAMPLE_RATE_44100, FSKConfig.PCM_8BIT, FSKConfig.CHANNELS_STEREO, FSKConfig.SOFT_MODEM_MODE_6, FSKConfig.THRESHOLD_20P);
			mAudioTrack = new AudioTrack(AudioManager.STREAM_MUSIC,mConfig.sampleRate, AudioFormat.CHANNEL_OUT_STEREO,AudioFormat.ENCODING_PCM_8BIT, pwMinBufferSize,AudioTrack.MODE_STATIC);
		} catch (IOException e1) {
			Log.e(TAG, "error:" + e1.getMessage());
		}
		/// INIT FSK ENCODER
		mEncoder = new FSKEncoder(mConfig, new FSKEncoderCallback() {
			@Override
			public void encoded(byte[] pcm8, short[] pcm16) {
				if (mConfig.pcmFormat == FSKConfig.PCM_8BIT) {
					//8bit buffer is populated, 16bit buffer is null
					//mAudioTrack.write(pcm8, 0, pcm8.length);
					//mAudioTrack.flush();//鍒锋柊  
//					mAudioTrack.setStereoVolume(1, 1);//璁剧疆宸﹀彸澹伴亾鎾斁闊抽噺  
//					mAudioTrack.setAuxEffectSendLevel(1.0f);
//					mAudioTrack.setLoopPoints(0, EncoderCore.getPowerSupplyBufferSize(), -1);//璁剧疆闊抽鎾斁寰幆鐐�   
					Log.d(TAG, "pwMinBufferSize:" + pwMinBufferSize);
					mAudioTrack = new AudioTrack(AudioManager.STREAM_MUSIC,mConfig.sampleRate, AudioFormat.CHANNEL_OUT_STEREO,AudioFormat.ENCODING_PCM_8BIT, pcm8.length,AudioTrack.MODE_STATIC);
					mAudioTrack.write(pcm8, 0, pcm8.length);
					mAudioTrack.play();//寮�鎾斁
					//mAudioTrack.play();
					try {
						int durtion = (int)((pcm8.length) * ( 1000 /(float)mConfig.sampleRate ) + 300) ;
						Thread.sleep(durtion);
						mAudioTrack.release();
					} catch (InterruptedException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
				}
				else if (mConfig.pcmFormat == FSKConfig.PCM_16BIT) {
					//16bit buffer is populated, 8bit buffer is null
					mAudioTrack.write(pcm16, 0, pcm16.length);
				}
			}
		});
		
	}

	public void transmit(int[] cmd,boolean study) {
//	    mAudioTrack.play();
		mEncoder.studyStatus(study);
	    mEncoder.clearData();
	    int[] data =  cmd ;
		if (data.length > FSKConfig.ENCODER_DATA_BUFFER_SIZE) {
			//chunk data
			int[] buffer = new int[FSKConfig.ENCODER_DATA_BUFFER_SIZE];
			IntBuffer dataFeed = IntBuffer.wrap(data);
			while (dataFeed.remaining() > 0) {
				if (dataFeed.remaining() < buffer.length) {
					buffer = new int[dataFeed.remaining()];
				}
				dataFeed.get(buffer);
				mEncoder.appendData(buffer);
				try {
					Thread.sleep(100); //wait for encoder to do its job, to avoid buffer overflow and data rejection
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
			}
		}
		else {
			mEncoder.appendData(data);
		}
	}
	
	public void stop(){
		mEncoder.stop();
		mAudioTrack.stop();
		mAudioTrack.release();
	}
}
